﻿using System;
using System.Collections.Generic;
using System.IO;

namespace Utility
{
    public static class StringExtensions
    {
        public static DateTime? ToNullableDateTime(this string text)
        {
            if (!string.IsNullOrEmpty(text))
            {
                DateTime value;
                if (DateTime.TryParse(text, out value))
                    return value;
            }
            return null;
        }

        public static string ToSafeCsvString(this string s)
        {
            if (string.IsNullOrEmpty(s))
                return string.Empty;
            int index = s.IndexOfAny(new[] { ' ', '\t', '\r', '\n', '\"', ',' });
            return index >= 0 ? "\"" + s.Replace("\"", "\"\"") + "\"" : s;
        }

        public static IEnumerable<string> ParseCsv(this string text)
        {
            IList<string> values = new List<string>();

            using (var reader = new StringReader(text))
            {
                string value = string.Empty;
                for (; ; )
                {
                    var c = reader.Peek();
                    if (c == -1)
                    {
                        values.Add(value == string.Empty ? null : value);
                        break;
                    }
                    if (c == '\"')
                    {
                        //consume "
                        reader.Read();

                        for (; ; )
                        {
                            var d = reader.Read();
                            if (d == -1)
                                throw new EndOfStreamException("Unexpected end of stream");
                            var n = reader.Peek();
                            if (d == '\"' && n == '\"')
                                reader.Read(); //skip the next quote but append this quote
                            else if (d == '\"')
                                break;
                            value += (char)d;
                        }
                    }
                    else if (c == ',')
                    {
                        //consume ,
                        reader.Read();

                        values.Add(value == string.Empty ? null : value);
                        value = string.Empty;
                    }
                    else
                    {
                        //consume char
                        reader.Read();

                        value += (char)c;
                    }
                }
            }

            return values;
        }
    }
}
